package com.travel.server.manager.impl.command.order;

import com.travel.common.CommonConstant;
import com.travel.common.util.CollectionUtil;
import com.travel.common.util.CommonUtil;
import com.travel.common.util.DateUtil;
import com.travel.server.manager.dto.request.order.QueryOrderListRequest;
import com.travel.server.manager.dto.response.order.QueryOrderListResponse;
import com.travel.server.manager.dto.response.order.QueryOrderListResponse.OrderItem;
import com.travel.server.manager.impl.command.AbstractCommand;
import com.travel.server.manager.impl.dal.*;
import com.travel.server.manager.impl.dal.OrderDal.OrderInfoParam;
import com.travel.server.manager.impl.dal.ProjectDal.ProjectParam;
import com.travel.server.manager.impl.dal.SpecialDal.SpecialParam;
import com.travel.server.manager.impl.enums.OrderRefundEnum;
import com.travel.server.manager.impl.sal.CustomerSal;
import com.travel.server.manager.impl.sal.OrderSal;
import com.travel.server.manager.model.CustomerInfo;
import com.travel.server.manager.model.ProjectInfo;
import com.travel.server.manager.model.ProjectSpecial;
import com.travel.server.manager.model.UserInfo;
import com.travel.server.manager.model.dto.OrderExcelDto;
import com.travel.server.manager.model.dto.OrderItemDto;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

/**
 * @Author: LiZhenhui
 * @Date: 2018/11/5 18:13
 * @Desc:
 */
@Component
@Slf4j
public class QueryOrderListCommand extends AbstractCommand<QueryOrderListRequest, QueryOrderListResponse> {

    @Autowired
    private OrderDal orderDal;

    @Autowired
    private ProjectDal projectDal;

    @Autowired
    private SpecialDal specialDal;

    @Autowired
    private UserDal userDal;

    @Autowired
    private CustomerDal customerDal;

    private final static String REFUND_ING = "退款处理中";

    private final static String REFUND_END = "退款结束";

    @Override
    protected void checkInput(QueryOrderListRequest request) {
        if(request.getLabel() == null){
            throwInvalidParam();
        }
    }

    @Override
    public QueryOrderListResponse handle(QueryOrderListRequest request) {
        checkInput(request);

        QueryOrderListResponse response = new QueryOrderListResponse();
        OrderInfoParam param = makeOrderInfoParam(request);
        if(param == null){
            return response;
        }
        PageDto<OrderItemDto> pageDto = orderDal.select(param);
        return makeResponse(pageDto);
    }

    public List<List<Object>> makeExcelData(QueryOrderListRequest request){
        OrderInfoParam param = makeOrderInfoParam(request);
        if(param == null){
            return null;
        }

        List<OrderExcelDto> excelList = orderDal.selectExcelData(param);
        if(CollectionUtil.isEmpty(excelList)){
            return null;
        }

        List<List<Object>> list = new ArrayList<>();
        for(OrderExcelDto dto : excelList){
            List<Object> row = new ArrayList<>();
            // 订单编号, 项目名称, 出团编号, 出行日期, 优惠, 小计, 客户姓名, 性别, 手机, 微信, 邮箱, 收货地址, 备注
            row.add(dto.getOrderId());
            row.add(dto.getProjectName());
            row.add(dto.getTeamNumber());
            if(dto.getTravelDate() != null) {
                row.add(DateUtil.dateToStr(dto.getTravelDate(), DateUtil.YYYY_MM_DD));
            }else{
                row.add(CommonConstant.EMPTY_STR);
            }
            if(dto.getDiscountAmount() != null) {
                row.add(CommonUtil.fenToYuan(dto.getDiscountAmount()));
            }else {
                row.add(CommonConstant.EMPTY_STR);
            }
            if(dto.getOrderAmount() != null) {
                row.add(CommonUtil.fenToYuan(dto.getOrderAmount()));
            }else {
                row.add(CommonConstant.EMPTY_STR);
            }
            row.add(dto.getCustomerName());
            row.add(dto.getSex());
            row.add(dto.getMobile());
            row.add(dto.getWechatNumber());
            row.add(dto.getMail());
            if(StringUtils.isNotBlank(dto.getCollectAddress())) {
                row.add(dto.getCollectAddress());
            }else{
                CustomerInfo customerInfo = new CustomerInfo();
                customerInfo.setLiveCountry(dto.getLiveCountry());
                customerInfo.setLiveProvince(dto.getLiveProvince());
                customerInfo.setLiveCity(dto.getLiveCity());
                customerInfo.setLiveArea(dto.getLiveArea());
                customerInfo.setLiveAddress(dto.getLiveAddress());
                row.add(CustomerSal.getCollectAddress(customerInfo));
            }
            row.add(dto.getNote());
            list.add(row);
        }
        return list;
    }

    private QueryOrderListResponse makeResponse(PageDto<OrderItemDto> pageDto){
        QueryOrderListResponse response = new QueryOrderListResponse();
        response.setTotalNum(pageDto.getTotal());
        List<OrderItem> itemList = new ArrayList<>();
        List<OrderItemDto> list = pageDto.getList();
        if(!CollectionUtil.isEmpty(list)){
            for(OrderItemDto itemDto : list){
                OrderItem orderItem = new OrderItem();
                orderItem.setBuyer(itemDto.getBuyer());
                orderItem.setCommodityName(itemDto.getCommodityName());
                orderItem.setId(itemDto.getId());
                orderItem.setIsTravelData(itemDto.getIsTravelData());
                orderItem.setNeedEnglish(itemDto.getNeedEnglish());
                orderItem.setNote(itemDto.getNote());
                if(itemDto.getOrderAmount() != null) {
                    orderItem.setOrderAmount(CommonUtil.fenToYuan(itemDto.getOrderAmount()).toString());
                }
                orderItem.setOrderChargeName(itemDto.getOrderChargeName());
                orderItem.setOrderId(itemDto.getOrderId());
                orderItem.setOrderStars(itemDto.getOrderStars());
                orderItem.setOrderTime(itemDto.getOrderTime());
                orderItem.setOrderTotal(itemDto.getOrderTotal());
                orderItem.setOrderType(itemDto.getOrderType());
                orderItem.setOutOrderId(itemDto.getOutOrderId());
                if(itemDto.getPayAmount() != null) {
                    orderItem.setPayAmount(CommonUtil.fenToYuan(itemDto.getPayAmount()).toString());
                }
                orderItem.setPayId(itemDto.getPayId());
                orderItem.setPayType(itemDto.getPayType());
                orderItem.setProjectPicUrl(itemDto.getProjectPicUrl());
                orderItem.setStep(itemDto.getStep());
                orderItem.setTeamNumber(itemDto.getTeamNumber());
                orderItem.setTravelDate(itemDto.getTravelDate());
                itemList.add(orderItem);
            }
        }
        response.setOrderList(itemList);
        return response;
    }

    private OrderInfoParam makeOrderInfoParam(QueryOrderListRequest request){
        OrderInfoParam param = new OrderInfoParam();
        if(request.getLabel() != null){
            param.setStepList(OrderSal.getStepList(request.getLabel()));
        }
        if(StringUtils.isNotBlank(request.getStartPayTime())){
            param.setStartOrderTime(DateUtil.strToDate(request.getStartPayTime(), DateUtil.YYYY_MM_DD));
        }
        if(StringUtils.isNotBlank(request.getEndPayTime())){
            param.setEndOrderTime(DateUtil.strToDate(request.getEndPayTime(), DateUtil.YYYY_MM_DD));
        }
        if(StringUtils.isNotBlank(request.getOrderChargeName())){
            List<Integer> userIdList = selectUserIdList(request.getOrderChargeName());
            if(!CollectionUtil.isEmpty(userIdList)){
                param.setOrderChargeIdList(userIdList);
            }else{
                return null;
            }
        }
        if(StringUtils.isNotBlank(request.getOrderId())){
            param.setOrderId(request.getOrderId());
        }
        if(StringUtils.isNotBlank(request.getOrderState())){
            param.setOrderState(request.getOrderState());
        }
        if(StringUtils.isNotBlank(request.getOrderType())){
            param.setOrderType(request.getOrderType());
        }
        if(StringUtils.isNotBlank(request.getOutOrderId())){
            param.setOutOrderId(request.getOutOrderId());
        }
        if(StringUtils.isNotBlank(request.getPayId())){
            param.setPayId(request.getPayId());
        }
        if(StringUtils.isNotBlank(request.getPayType())){
            param.setPayType(request.getPayType());
        }
        if(request.getIsStars() != null){
            param.setIsStars(request.getIsStars());
        }
        if(request.getOffset() != null && request.getLimit() != null) {
            param.setOffset(request.getOffset());
            param.setLimit(request.getLimit());
        }

        if(StringUtils.isNotBlank(request.getCollectName()) || StringUtils.isNotBlank(request.getCollectMobile())){
            CustomerDal.CustomerParam customerParam = new CustomerDal.CustomerParam();
            if(StringUtils.isNotBlank(request.getCollectName())){
                customerParam.setName(request.getCollectName());
            }
            if(StringUtils.isNotBlank(request.getCollectMobile())){
                customerParam.setMobile(request.getCollectMobile());
            }
            List<CustomerInfo> customerInfoList = customerDal.selectByExample(customerParam);
            if(CollectionUtil.isEmpty(customerInfoList)){
                return null;
            }
            List<Integer> customerIdList = new ArrayList<>();
            for(CustomerInfo customerInfo : customerInfoList){
                customerIdList.add(customerInfo.getId());
            }
            param.setCustomerIdList(customerIdList);
        }

        return makeOtherParam(request, param);
    }

    private OrderInfoParam makeOtherParam(QueryOrderListRequest request, OrderInfoParam param){
        //根据项目、项目名查询对应项目，项目下规格
        if(StringUtils.isNotBlank(request.getCommodityName())){
            ProjectParam projectParam1 = new ProjectParam();
            projectParam1.setName(request.getCommodityName());
            List<ProjectInfo> projectInfoList = projectDal.selectByExample(projectParam1);

            ProjectParam projectParam2 = new ProjectParam();
            projectParam2.setProjectGroup(request.getCommodityName());
            List<ProjectInfo> projectInfoList2 = projectDal.selectByExample(projectParam2);

            projectInfoList.addAll(projectInfoList2);
            if(!CollectionUtil.isEmpty(projectInfoList)){
                List<Integer> projectIdList = new ArrayList<>();
                for(ProjectInfo projectInfo : projectInfoList){
                    projectIdList.add(projectInfo.getId());
                }
                SpecialParam specialParam = new SpecialParam();
                specialParam.setProjectIdList(projectIdList);
                List<ProjectSpecial> specialList = specialDal.selectByExample(specialParam);
                if(!CollectionUtil.isEmpty(specialList)){
                    List<Integer> specialIdList = new ArrayList<>();
                    for(ProjectSpecial projectSpecial : specialList){
                        specialIdList.add(projectSpecial.getId());
                    }
                    param.setSpecialIdList(specialIdList);
                }
            }else{
                return null;
            }
        }

        //维权状态，查询退款记录
        if(StringUtils.isNotBlank(request.getRightState())){
            List<String> refundStateList = null;
            if(REFUND_ING.equals(request.getRightState())){
                refundStateList = Arrays.asList(OrderRefundEnum.AGREE.getState(), OrderRefundEnum.APPLY.getState(), OrderRefundEnum.RETURN.getState());
            }else if(REFUND_END.equals(request.getRightState())){
                refundStateList = Arrays.asList(OrderRefundEnum.CLOSE.getState(), OrderRefundEnum.SUCCESS.getState(), OrderRefundEnum.REJECT.getState());
            }
            param.setRefundStateList(refundStateList);
        }

        return param;
    }

    private List<Integer> selectUserIdList(String name){
        UserDal.UserParam param = new UserDal.UserParam();
        param.setName(name);
        List<UserInfo> userList = userDal.selectByExample(param);
        if(CollectionUtil.isEmpty(userList)){
            return null;
        }
        List<Integer> idList = new ArrayList<>();
        for(UserInfo userInfo : userList){
            idList.add(userInfo.getId());
        }
        return idList;
    }
}
